package com.boful.convert.core.impl;

import java.io.File;
import java.io.FileNotFoundException;
import java.io.IOException;

import org.apache.log4j.Logger;

import com.boful.convert.core.TranscodeEvent;
import com.boful.convert.core.impl.utils.FFMpegUtils;
import com.boful.convert.core.impl.utils.MencoderUtils;
import com.boful.convert.model.DiskFile;

class VideoConvert {

	private static Logger logger = Logger.getLogger(VideoConvert.class);
	private String ffmpegPath;
	private String mencoderPath;
	private String mediaInfoPath;
	private String mp4BoxPath;

	private class ConvertThread implements Runnable {
		private DiskFile src;
		private DiskFile dest;
		private int width;
		private int height;
		private TranscodeEvent transcodeEvent;
		private String jobId;

		public ConvertThread(DiskFile src, DiskFile dest, int width, int height, TranscodeEvent transcodeEvent,
				String jobId) {
			super();
			this.src = src;
			this.dest = dest;
			this.width = width;
			this.height = height;
			this.transcodeEvent = transcodeEvent;
			this.jobId = jobId;
		}

		public DiskFile getSrc() {
			return src;
		}

		public void setSrc(DiskFile src) {
			this.src = src;
		}

		public DiskFile getDest() {
			return dest;
		}

		public void setDest(DiskFile dest) {
			this.dest = dest;
		}

		public int getWidth() {
			return width;
		}

		public void setWidth(int width) {
			this.width = width;
		}

		public int getHeight() {
			return height;
		}

		public void setHeight(int height) {
			this.height = height;
		}

		public TranscodeEvent getTranscodeEvent() {
			return transcodeEvent;
		}

		public void setTranscodeEvent(TranscodeEvent transcodeEvent) {
			this.transcodeEvent = transcodeEvent;
		}

		public String getJobId() {
			return jobId;
		}

		public void setJobId(String jobId) {
			this.jobId = jobId;
		}

		@Override
		public void run() {
			try {
				FFMpegUtils.transcode(ffmpegPath, mediaInfoPath, src.getAbsolutePath(), dest.getAbsolutePath(),
						width + "x" + height, transcodeEvent, jobId);
				System.out.println("mp4 dest file exsit:" + dest.exists());
				if (dest.exists() && getMp4BoxPath() != null) {
					fixIECache(dest);
				}
			} catch (FileNotFoundException e) {
				logger.error(e.getMessage(), e);
				transcodeEvent.onTranscodeFail(src, e.getMessage(), jobId);
			} catch (IOException e) {
				transcodeEvent.onTranscodeFail(src, e.getMessage(), jobId);
			}
		}

	}

	public void convert(DiskFile src, DiskFile dest, int width, int height, int videoBitrate, int audioBitrate,
			TranscodeEvent transcodeEvent, String jobId) {
		ConvertThread convertThread = new ConvertThread(src, dest, width, height, transcodeEvent, jobId);
		Thread thread = new Thread(convertThread);
		thread.start();
	}

	private void fixIECache(DiskFile mp4File) {
		File mp4Box = new File(getMp4BoxPath());
		if (!mp4Box.exists()) {
			return;
		}
		StringBuffer sb = new StringBuffer(getMp4BoxPath());
		sb.append("  -inter 500 ");
		sb.append(mp4File.getAbsolutePath());

		Runtime runtime = Runtime.getRuntime();
		try {
			Process process = runtime.exec(sb.toString());
			int wait = process.waitFor();
			logger.info(mp4File.getAbsolutePath() + "转码成功!" + wait);
		} catch (Exception e) {
			e.printStackTrace();
		}
	}

	private void convertRmvbToMp4(DiskFile src, DiskFile dest, int width, int height, int videoBitrate,
			int audioBitrate, TranscodeEvent transcodeEvent, String jobId) {
		try {
			MencoderUtils mencoderUtils = new MencoderUtils(mencoderPath, ffmpegPath, mediaInfoPath, width, height,
					videoBitrate, audioBitrate, transcodeEvent, src, dest);
			mencoderUtils.transcodeToAVI(jobId);

		} catch (FileNotFoundException e) {
			logger.error(e.getMessage(), e);
			if (transcodeEvent != null) {
				transcodeEvent.onTranscodeFail(src, e.getMessage(), jobId);
			}

		} catch (IOException e) {
			logger.error(e.getMessage(), e);
			if (transcodeEvent != null) {
				transcodeEvent.onTranscodeFail(src, e.getMessage(), jobId);
			}
		}
	}

	public String getFfmpegPath() {
		return ffmpegPath;
	}

	public void setFfmpegPath(String ffmpegPath) {
		this.ffmpegPath = ffmpegPath;
	}

	public String getMencoderPath() {
		return mencoderPath;
	}

	public void setMencoderPath(String mencoderPath) {
		this.mencoderPath = mencoderPath;
	}

	public String getMediaInfoPath() {
		return mediaInfoPath;
	}

	public void setMediaInfoPath(String mediaInfoPath) {
		this.mediaInfoPath = mediaInfoPath;
	}

	public String getMp4BoxPath() {
		return mp4BoxPath;
	}

	public void setMp4BoxPath(String mp4BoxPath) {
		this.mp4BoxPath = mp4BoxPath;
	}

}
